from machine import Timer
import my_lib
import utime
from speech_recognizer import asr
from Maix import GPIO, I2S
from fpioa_manager import fm
import socket
import network
import gc
import os
import machine
from fpioa_manager import fm
from board import board_info
import time

fm.register(20, fm.fpioa.I2S0_IN_D0, force=True)
fm.register(32, fm.fpioa.I2S0_SCLK, force=True)  # dock 32
fm.register(30, fm.fpioa.I2S0_WS, force=True)   # dock 30

rx = I2S(I2S.DEVICE_0)
rx.channel_config(rx.CHANNEL_0, rx.RECEIVER, align_mode=I2S.STANDARD_MODE)
rx.set_sample_rate(16000)
print(rx)


#需要修改的地方
wifiName = "ReiholdAP"                   #wifi 名称，不支持5G wifi
wifiPassword = "13172740961."       #wifi 密码
clientID = "cbf10a41475b46db9053a026db09b3f5"            # Client ID ，密钥，巴法云控制台获取
myTopic='k210irremote'                     # 需要订阅的主题值，巴法MQTT控制台创建

#默认设置
serverIP = 'bemfa.com'    # mqtt 服务器地址
port = 8344

class maix_asr(asr):
    asr_vocab = ["lv", "shi", "yang", "chun", "yan", "jing", "da", "kuai", "wen", "zhang", "de", "di", \
        "se", "si", "yue", "lin", "luan", "geng", "xian", "huo", "xiu", "mei", "yi", "ang", "ran", "ta",\
            "jin", "ping", "yao", "bu", "li", "liang", "zai", "yong", "dao", "shang", "xia", "fan", "teng",\
            "dong", "she", "xing", "zhuang", "ru", "hai", "tun", "zhi", "tou", "you", "ling", "pao",\
            "hao", "le", "zha", "zen", "me", "zheng", "cai", "ya", "shu", "tuo", "qu", "fu", "guang",\
            "bang", "zi", "chong", "shui", "cuan", "ke", "shei", "wan", "hou", "zhao", "jian", "zuo", "cu",\
                 "hei", "yu", "ce", "ming", "dui", "cheng", "men", "wo", "bei", "dai", "zhe", "hu", "jiao", 
                 "pang", "ji", "lao", "nong", "kang", "yuan", "chao", "hui", "xiang", "bing", "qi", "chang", 
                 "nian", "jia", "tu", "bi", "pin", "xi", "zou", "chu", "cun", "wang", "na", "ge", "an", "ning",
                  "tian", "xiao", "zhong", "shen", "nan", "er", "ri", "zhu", "xin", "wai", "luo", "gang", "qing", 
                  "xun", "te", "cong", "gan", "lai", "he", "dan", "wei", "die", "kai", "ci", "gu", "neng", "ba", 
                  "bao", "xue", "shuai", "dou", "cao", "mao", "bo", "zhou", "lie", "qie", "ju", "chuan", "guo", 
                  "lan", "ni", "tang", "ban", "su", "quan", "huan", "ying", "a", "min", "meng", "wu", "tai",
                   "hua", "xie", "pai", "huang", "gua", "jiang", "pian", "ma", "jie", "wa", "san", "ka",
                    "zong", "nv", "gao", "ye", "biao", "bie", "zui", "ren", "jun", "duo", "ze", "tan",
                     "mu", "gui", "qiu", "bai", "sang", "jiu", "yin", "huai", "rang", "zan", "shuo", "sha", "ben",
            "yun", "la", "cuo", "hang", "ha", "tuan", "gong", "shan", "ai", "kou", "zhen", "qiong", 
            "ding", "dang", "que", "weng", "qian", "feng", "jue", "zhuan", "ceng", "zu", "bian", "nei",
             "sheng", "chan", "zao", "fang", "qin", "e", "lian", "fa", "lu", "sun", "xu", "deng", 
             "guan", "shou", "mo", "zhan", "po", "pi", "gun", "shuang", "qiang", "kao", "hong", 
             "kan", "dian", "kong", "pei", "tong", "ting", "zang", "kuang", "reng", "ti", "pan",
              "heng", "chi", "lun", "kun", "han", "lei", "zuan", "man", "sen", "duan", "leng",
               "sui", "gai", "ga", "fou", "kuo", "ou", "suo", "sou", "nu", "du", "mian", "chou",
                "hen", "kua", "shao", "rou", "xuan", "can", "sai", "dun", "niao", "chui", 
                "chen", "hun", "peng", "fen", "cang", "gen", "shua", "chuo", "shun", "cha", 
                "gou", "mai", "liu", "diao", "tao", "niu", "mi", "chai", "long", "guai", "xiong", 
                "mou", "rong", "ku", "song", "che", "sao", "piao", "pu", "tui", "lang", "chuang", 
                "keng", "liao", "miao", "zhui", "nai", "lou", "bin", "juan", "zhua", "run", "zeng",
                 "ao", "re", "pa", "qun", "lia", "cou", "tie", "zhai", "kuan", "kui", "cui", "mie", 
                 "fei", "tiao", "nuo", "gei", "ca", "zhun", "nie", "mang", "zhuo", "pen", "zun", "niang", 
                 "suan", "nao", "ruan", "qiao", "fo", "rui", "rao", "ruo", "zei", "en", "za", "diu",
                 "nve", "sa", "nin", "shai", "nen", "ken", "chuai", "shuan", "beng", "ne", "lve", "qia",
                  "jiong", "pie", "seng", "nuan", "nang", "miu", "pou", "cen", "dia", "o", "zhuai", "yo",
                   "dei", "n", "ei", "nou", "bia", "eng", "den", "_"]

    def get_asr_list(string='xiao-ai-fas-tong-xue'):
        return [__class__.asr_vocab.index(t) for t in string.split('-') if t in __class__.asr_vocab]

    def get_asr_string(listobj=[117, 214, 257, 144]):
        return '-'.join([__class__.asr_vocab[t] for t in listobj if t < len(__class__.asr_vocab)])

    def unit_test():
        print(__class__.get_asr_list('xiao-ai'))
        print(__class__.get_asr_string(
            __class__.get_asr_list('xiao-ai-fas-tong-xue')))

    def config(self, sets):
        self.set([(sets[key], __class__.get_asr_list(key)) for key in sets])

    def recognize(self):
        res = self.result()
        # print(tmp)
        if res != None:
            sets = {}
            for tmp in res:
                sets[__class__.get_asr_string(tmp[1])] = tmp[0]
                #print(tmp[0], get_asr_string(tmp[1]))
            return sets
        return None



# WIFI 连接函数   maixpy 适配完成
def do_connect():
    fm.register(7,fm.fpioa.UART2_TX) # wifi的引脚，详见
                                     # https://github.com/sipeed/MaixPy_scripts
                                     # /blob/master/board/config_maix_dock.py 配置文件
    fm.register(6,fm.fpioa.UART2_RX)
    uart = machine.UART(machine.UART.UART2,115200,timeout=1000, read_buf_len=4096)
    nic=network.ESP8285(uart)
    nic.connect(wifiName,wifiPassword)
    if not nic.isconnected():
        print('connecting to network...')
        nic.connect(wifiName, wifiPassword)
        while not nic.isconnected():
            pass
    print('connect  WiFi ok')



# tcp 客户端初始化 #TODO
def connect_and_subscribe():
  addr_info = socket.getaddrinfo(serverIP, port)
  addr = addr_info[0][-1]
  client = socket.socket(socket.AF_INET, socket.SOCK_STREAM)   # 创建TCP的套接字,也可以不给定参数。默认为TCP通讯方式
  client.connect(addr)                                 # 设置要连接的服务器端的IP和端口,并连接
  substr = 'cmd=1&uid='+clientID+'&topic='+myTopic+'\r\n'
  client.send(substr.encode("utf-8"))
  print("Connected to %s" % serverIP)
  return client

#心跳 #TODO
def Ping(self):
    # 发送心跳
    try:
        keeplive = 'ping\r\n'
        client.send(keeplive.encode("utf-8"))
    except:
        restart_and_reconnect()

# 重新连接  #TODO
def restart_and_reconnect():
  print('Failed to connect to TCP  broker. Reconnecting...')
  time.sleep(10)
  machine.reset()


def on_timer(timer):
    #print("time up:",timer)
    # print("param:",timer.callback_arg())
    timer.callback_arg().state()


try:
    # 连接局域网wifi
    do_connect()

    #开始连接TCP
    try:
        client = connect_and_subscribe()
    except OSError as e:
        restart_and_reconnect()

    # 与巴法云的ping连接, 保持心跳连接, 配置周期回调
    #tim2 = Timer(Timer.TIMER0, Timer.CHANNEL1, mode=Timer.MODE_PERIODIC, period=10000, callback=Ping )
    #tim2.start()

    # default: maix dock / maix duino set shift=0
    t = maix_asr(0x500000, I2S.DEVICE_0, 3, shift=0)  # maix bit set shift=1
    tim = Timer(Timer.TIMER2, Timer.CHANNEL0,
                mode=Timer.MODE_PERIODIC, period=64, callback=on_timer, arg=t)

    t.config({
        'da-kai': 0.3,
        'guan-bi': 0.3,
    })

    print(t.get())

    while True:
        # time.sleep(1)
        tmp = t.recognize()            
        print(tmp)
        if tmp != None:
            # print(tmp)
            print(type(list(tmp.keys())[0]))
            print(list(tmp.keys())[0])
            tim.stop()
            t.stop()
            if list(tmp.keys())[0] == "guan-bi":
                print("guanbi")
                my_lib.ir_send_gree_off()
            if list(tmp.keys())[0] == "da-kai":
                print("dakai")
                my_lib.ir_send_gree()

        data = client.recv(128)                         # 从服务器端套接字中读取字节数据
        if(len(data) != 0):                             # 如果接收数据为0字节时,关闭套接字
            data=data.decode('utf-8')
            print(data.strip())                         # 去掉尾部回车换行符，并打印接收到的字符
        
        # 录音设备开始录音
        tim.restart()
        t.run()

except Exception as e:  # 如果出错就重新启动
    print(e)
    print('or Failed to connect to  broker. Reconnecting...')
    restart_and_reconnect()

finally:
    tim.stop()
    tim2.stop()
    t.__del__()
    del t
